/*
 * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *       http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package io.iec.edp.caf.rpc.client.grpc.interceptor;

import io.grpc.*;
import io.iec.edp.caf.boot.context.CAFContext;
import io.iec.edp.caf.common.JSONSerializer;
import io.iec.edp.caf.rpc.api.grpc.annotation.GrpcClientInterceptor;
import io.iec.edp.caf.rpc.api.grpc.variable.GrpcVariable;
import lombok.extern.slf4j.Slf4j;

@Slf4j
@GrpcClientInterceptor
public class CafGrpcClientInterceptor implements ClientInterceptor {

    private static int times = 0;

    @Override
    public <ReqT, RespT> ClientCall<ReqT, RespT> interceptCall(MethodDescriptor<ReqT, RespT> method, CallOptions callOptions, Channel next) {
        return new ForwardingClientCall.SimpleForwardingClientCall<ReqT, RespT>(next.newCall(method, callOptions)) {

            //可以拦截不同阶段
            @Override
            public void start(Listener<RespT> responseListener, Metadata headers) {
                headers.put(GrpcVariable.SESSION_ID, CAFContext.current.getSessionId());
                headers.put(GrpcVariable.SESSION,JSONSerializer.serialize(CAFContext.current.getCurrentSession()));
                headers.put(GrpcVariable.CONTEXT,JSONSerializer.serialize(CAFContext.current));
                //super.start(responseListener, headers);
                super.start(new ForwardingClientCallListener.SimpleForwardingClientCallListener<RespT>(responseListener) {
                    @Override
                    public void onHeaders(Metadata headers) {
                        /**
                         * if you don't need receive header from server, you can
                         * use {@link io.grpc.stub.MetadataUtils#attachHeaders}
                         * directly to send header
                         */
                        super.onHeaders(headers);
                    }
                }, headers);
                 }

            @Override
            public void request(int numMessages) {
                super.request(numMessages);
            }

            @Override
            public Attributes getAttributes() {
                return super.getAttributes();
            }

            @Override
            public void sendMessage(ReqT message) {
                //log.error("testMsg");
                super.sendMessage(message);
            }

        };
    }
}
